package com.foreveross.chameleon.manager;

import java.io.File;
import java.util.ArrayList;
import java.util.List;
import java.util.concurrent.ExecutionException;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;

import android.app.Service;
import android.content.Context;
import android.content.Intent;
import android.os.Binder;
import android.os.Environment;
import android.os.IBinder;
import android.util.Log;
import android.widget.Toast;

import com.foreveross.chameleon.config.ChameleonConfig;
import com.foreveross.chameleon.config.ChameleonConstants;
import com.foreveross.chameleon.model.ApplicationInfo;
import com.foreveross.chameleon.model.ModuleInfo;
import com.foreveross.chameleon.task.CheckDependsTask;
import com.foreveross.chameleon.task.DownloadFileAsyncTask;
import com.foreveross.chameleon.task.UnZipAndInstallModuleTask;
import com.foreveross.chameleon.utils.FileCopeTool;
import com.foreveross.chameleon.utils.ThreadPlatformUtils;
import com.google.gson.Gson;
import com.google.gson.GsonBuilder;

public class ModuleOperationService extends Service {

    private ExecutorService pool = Executors.newFixedThreadPool(3);

    public class ModuleOperationServiceBinder extends Binder {
        public ModuleOperationService getService() {
            return ModuleOperationService.this;
        }
    }

    @Override
    public IBinder onBind(Intent intent) {
        return new ModuleOperationServiceBinder();
    }

    @Override
    public void onRebind(Intent intent) {
        super.onRebind(intent);
    }

    public static Intent getIntent(Context context) {
        return new Intent(context, ModuleOperationService.class);
    }

    public void install(final ModuleInfo module) {

        DownloadFileAsyncTask task = new DownloadFileAsyncTask(this) {

        	int cur_progress = 0;
            @Override
            public void doPreExecuteWithoutDialog() {
                super.doPreExecuteWithoutDialog();
                module.setModuleType(ModuleInfo.INSTALLING);
                BroadcastManager.getInstance().sendModuleDownloadStart(module);
            }

            @Override
            protected void onProgressUpdate(Integer... progress) {
                super.onProgressUpdate(progress);
                int p = progress[0];
                module.setProgress(p);
                if(p - cur_progress >= 5 || p >= 100) {
                	cur_progress = p;
                	BroadcastManager.getInstance().sendModuleUpdateProgress(module,p);
                }
            }

            @Override
            protected void doPostExecute(String result) {
                super.doPostExecute(result);
                final ApplicationInfo cubeApplication = ApplicationInfo.getInstance(context);

                UnZipAndInstallModuleTask unZipTask = new UnZipAndInstallModuleTask(ModuleOperationService.this, cubeApplication, module) {

                    @Override
                    protected void onPreExecute() {
                        super.onPreExecute();
                    }

                    @Override
                    protected void onPostExecute(Boolean result) {
                        super.onPostExecute(result);
                        if(result) {
                            module.setModuleType(ModuleInfo.INSTALLED);
                            cubeApplication.removeModule(module.getIdentifier());
                            cubeApplication.getModules().add(module);
                            cubeApplication.save(cubeApplication);
                            AutoDownloadHelper.getInstance().finishDownload(module);
                            BroadcastManager.getInstance().sendModuleInstallState(module.getIdentifier(), true);
                            if(AutoDownloadHelper.getInstance().getProgressCount() == 0) {  //所有模块安装完成，清理下载列表
                                AutoDownloadHelper.getInstance().clear();
                                BroadcastManager.getInstance().sendModuleDownloadFinsh(module);
                            } else {
                            	BroadcastManager.getInstance().sendUpdateDownloadCount(AutoDownloadHelper.getInstance().getProgressCount());
                            }
                        } else {
                            if(module != null) {
                                module.setModuleType(ModuleInfo.UNINSTALL);
                                AutoDownloadHelper.getInstance().finishDownload(module);
                                BroadcastManager.getInstance().sendModuleDownloadFail(module);
                                BroadcastManager.getInstance().sendModuleInstallState(module.getIdentifier(), false);
                            }
                        }
                    }
                    ;
                };
                unZipTask.execute();

            }

            @Override
            protected void doHttpFail(Exception e) {
                super.doHttpFail(e);
                if(module != null) {
                    module.setModuleType(ModuleInfo.UNINSTALL);
                    AutoDownloadHelper.getInstance().finishDownload(module);
                    if(AutoDownloadHelper.getInstance().getProgressCount() == 0) {
                        AutoDownloadHelper.getInstance().clear();
                    } 
                    BroadcastManager.getInstance().sendModuleDownloadFail(module);
                    BroadcastManager.getInstance().sendModuleInstallState(module.getIdentifier(), false);
                }

            }

        };

        task.setShowProgressDialog(false);
        task.setNeedProgressDialog(false);
        ThreadPlatformUtils.executeByPalform(task,
                                             new String[]{module.getDownloadUrl(), module.getIdentifier() + ".zip",
                                                          DownloadFileAsyncTask.SDCARD,ChameleonConfig.APP_PACKAGENAME});
    }

    public boolean isExist(ModuleInfo cubeModule, String name) {
        String path = ChameleonConfig.APP_PATH + "/www/" + cubeModule.getIdentifier() + "/" + name;
        File f = new File(path);
        if(f.exists()) {
            return true;
        } else {
            return false;
        }
    }

    /**
     * 批量卸载模块
     * @param uninstallModules
     */
    public void batchUninstall(List<ModuleInfo> uninstallModules) {
    	for(ModuleInfo module : uninstallModules) {
    		uninstall(module);
    	}
    }
    
    /**
     * 卸载模块
     * @param cubeModule
     */
    public void uninstall(final ModuleInfo cubeModule) {
    	String moduleFile = ChameleonConfig.APP_PATH + "/" + cubeModule.getIdentifier() + ".zip";
    	String moduleDir = ChameleonConfig.APP_PATH + "/www/" + cubeModule.getIdentifier();	
    	boolean uninstall_state = false;
    	try{
    		File dir = new File(moduleDir);
    		if(dir.exists()) {
    			final ApplicationInfo appInfo = ApplicationInfo.getInstance(this);
    			appInfo.removeModule(cubeModule.getIdentifier());
    			appInfo.save(appInfo);
    			appInfo.tool.deleteFile(moduleFile);
    			appInfo.tool.deleteFolder(moduleDir);
    			uninstall_state = true;
    		}
    	}catch(Exception e){
    		uninstall_state = false;
    	}
    	BroadcastManager.getInstance().sendModuleUninstallState(cubeModule.getIdentifier(), uninstall_state);
    }

    public void upgrade(final ModuleInfo module) {

        DownloadFileAsyncTask task = new DownloadFileAsyncTask(this) {

        	int cur_progress = 0;
            @Override
            public void doPreExecuteWithoutDialog() {
                super.doPreExecuteWithoutDialog();
                module.setModuleType(ModuleInfo.UPGRADING);

            }

            @Override
            protected void onProgressUpdate(Integer... progress) {
                int p = progress[0];
                module.setProgress(p);
                if(p - cur_progress >= 5 || p >= 100) {
                	cur_progress = p;
                	BroadcastManager.getInstance().sendModuleUpdateProgress(module,p);
                }
                //	System.out.println("当前更新的模块是:"+module+"进度为:"+p);
                Log.v("downloadTask", " module " + module.getIdentifier() + " is download :" + p);
                
            }

            @Override
            protected void doPostExecute(String result) {
                super.doPostExecute(result);
                final ApplicationInfo cubeApplication = ApplicationInfo.getInstance(context);

                //BroadCastManager.sentModuleDownloadCount(context);
                UnZipAndInstallModuleTask unZipTask = new UnZipAndInstallModuleTask(ModuleOperationService.this, cubeApplication, module) {

                    @Override
                    protected Boolean doInBackground(String... params) {
                    	
                        // 先删除旧文件
                        StringBuilder sb2 = new StringBuilder();
                        sb2.append(ChameleonConfig.APP_PATH).append("/www/").append(module.getIdentifier());
                        cubeApplication.tool.deleteFolder(sb2.toString());
                        return super.doInBackground(params);
                    }

                    protected void onPostExecute(Boolean result) {
                        super.onPostExecute(result);
                        if(result) {
                            module.setModuleType(ModuleInfo.INSTALLED);
                            //cubeApplication.getModules().remove(module);
                            cubeApplication.removeModule(module.getIdentifier());
                            cubeApplication.getModules().add(module);
                            cubeApplication.save(cubeApplication);
                            AutoDownloadHelper.getInstance().finishDownload(module);
                            BroadcastManager.getInstance().sendModuleUpgradeState(module.getIdentifier(), true);
                            if(AutoDownloadHelper.getInstance().getProgressCount() == 0) {
                                AutoDownloadHelper.getInstance().clear();
                                BroadcastManager.getInstance().sendModuleDownloadFinsh(module);
                            }
                        } else {
                            module.setModuleType(ModuleInfo.UPGRADABLE);
                            module.setUpdatable(true);
                            AutoDownloadHelper.getInstance().finishDownload(module);
                            if(AutoDownloadHelper.getInstance().getProgressCount() == 0) {
                                AutoDownloadHelper.getInstance().clear();
                            } 
                            BroadcastManager.getInstance().sendModuleDownloadFail(module);
                            BroadcastManager.getInstance().sendModuleUpgradeState(module.getIdentifier(), false);
                        }
                    }
                    ;
                };
                unZipTask.execute();
            }

            @Override
            protected void doHttpFail(Exception e) {
                super.doHttpFail(e);
              
                module.setModuleType(ModuleInfo.UPGRADABLE);
                module.setUpdatable(true);
                AutoDownloadHelper.getInstance().finishDownload(module);
                if(AutoDownloadHelper.getInstance().getProgressCount() == 0) {
                    //模块下载完成
                	AutoDownloadHelper.getInstance().clear();
                    BroadcastManager.getInstance().sendModuleDownloadFinsh(module);
                }
                //Toast.makeText(context, "网络状态不稳定!", Toast.LENGTH_SHORT).show();
                BroadcastManager.getInstance().sendModuleUpgradeState(module.getIdentifier(), true);
            }

        };

        task.setShowProgressDialog(false);
        task.setNeedProgressDialog(false);
        ThreadPlatformUtils.executeByPalform(task,
                                             new String[]{module.getDownloadUrl(), module.getIdentifier() + ".zip",
                                                          DownloadFileAsyncTask.SDCARD, ChameleonConfig.APP_PACKAGENAME});

    }
    @Override
    public void onDestroy() {
        pool.shutdownNow();
    }

    public ArrayList<ModuleInfo> checkDepends(String identifier) {
        String path = ChameleonConfig.APP_PATH + "/www/";
        ArrayList<ModuleInfo> result = null;
        CheckDependsTask task = new CheckDependsTask() {

            @Override
            protected void onPostExecute(ArrayList<ModuleInfo> result) {
                super.onPostExecute(result);
                this.cancel(true);
                Log.e("check_tag", "task canceled");
            }

        };
        task.execute(identifier, path);
        try {
            result = task.get();
        } catch(InterruptedException e) {
            Log.e("checkDepends", "InterruptedException:检查依赖失败");
            try {
                result = task.get();
                return result;
            } catch(InterruptedException e1) {
                Log.e("checkDepends", "InterruptedException:检查依赖失败");
                e1.printStackTrace();
            } catch(ExecutionException e1) {
                Log.e("checkDepends", "ExecutionException:检查依赖失败");
                e1.printStackTrace();
            }
        } catch(ExecutionException e) {
            Log.e("checkDepends", "ExecutionException:检查依赖失败");
            e.printStackTrace();
        }
        return result;
    }



    public String getModuleUrl(final Context context, ModuleInfo module) {
        String identifier = module.getIdentifier();
        // 模块是否本地模块
        if(module.getLocal() == null) {
            String url = ChameleonConfig.APP_PATH + "/www/" + identifier;
            // 检查文件是否存在
            if(new FileCopeTool(context).isfileExist(url, "index.html")) {
                String moduleuUrl = "file:/" + url + "/index.html";
                return moduleuUrl;
            } else {
                Toast.makeText(context, "文件缺失，请重新下载", Toast.LENGTH_SHORT).show();
                return null;
            }
        } 
        return null;
    }

    

    public void cancelAutoDownload(List<ModuleInfo> modules) {
        saveAutoDownloadFile(modules);
    }

    public void autoDownload(List<ModuleInfo> modules) {

        int total = modules.size();
        for(ModuleInfo module : modules) {
        	AutoDownloadHelper.getInstance().addDownloadTask(module);
            install(module);
        }
        Intent intent = new Intent();
	    intent.setAction(ChameleonConstants.ACTION_MODULE_DOWNLOAD_START);
	    sendBroadcast(intent);
    }

    public void autoUpgrade(List<ModuleInfo> modules) {
		// TODO Auto-generated method stub
		int total = modules.size();
		for(ModuleInfo module : modules) {
			AutoDownloadHelper.getInstance().addDownloadTask(module);
			upgrade(module);
		}

		 Intent intent = new Intent();
	     intent.setAction(ChameleonConstants.ACTION_MODULE_DOWNLOAD_START);
	     sendBroadcast(intent);
	}
  
    public void saveAutoDownloadFile(List<ModuleInfo> modules) {
        ArrayList<String> list = new ArrayList<String>();
        for(ModuleInfo module : modules) {
            list.add(module.getIdentifier());
        }
        GsonBuilder builder = new GsonBuilder();
        Gson gson = builder.create();
        String json = gson.toJson(list);
        System.out.println(json);
        FileCopeTool tool = new FileCopeTool(getApplicationContext());
        tool.writeToJsonFile("autoDownLoadFile",
                             Environment.getExternalStorageDirectory().getPath() + "/" + ChameleonConfig.APP_PACKAGENAME + "/",
                             json);
    }

	


}
